package com.college.common.utils.security;

import org.apache.commons.codec.binary.Base64;

import javax.crypto.*;
import javax.crypto.spec.DESedeKeySpec;
import javax.crypto.spec.IvParameterSpec;
import java.io.UnsupportedEncodingException;
import java.security.InvalidAlgorithmParameterException;
import java.security.InvalidKeyException;
import java.security.Key;
import java.security.NoSuchAlgorithmException;
import java.security.spec.InvalidKeySpecException;

public class DESUtils {
    public static String code = "UTF-8";
    public static String key = "mgjr@3des123#dhjr9763089";

    public static void main(String[] args) {
        System.out.println(decrypt("DBwaRDJmogcZtNhLZWnW8U26+tZ4DcZng5CU/UqZ8jjuD8DTXT7936vZ8s3lR8Bk", "lH6>rG9]uB1!pZ3~oE1>dD7<", "2%8iTpSi"));
    }
    public static String encrypt(String data, String secretKey,String vi) {
        try {
            byte[] encrpyted = tripleDES(Cipher.ENCRYPT_MODE, data.getBytes(code), secretKey.getBytes(),vi.getBytes());
            byte[] encoded = Base64.encodeBase64(encrpyted); // Base64编码
            return new String(encoded);
        } catch (UnsupportedEncodingException e) {
            throw new RuntimeException(e);
        }
    }

    public static String decrypt(String data , String secretKey ,String vi) {
        try {
            byte[] decoded = Base64.decodeBase64(data); // Base64解码
            byte[] decrypted = tripleDES(Cipher.DECRYPT_MODE, decoded, secretKey.getBytes(),vi.getBytes());// 3DES解密
            return new String(decrypted, code);
        } catch (UnsupportedEncodingException e) {
            throw new RuntimeException(e);
        }
    }

    private static byte[] tripleDES(int opmode, byte[] data, byte[] secretKey ,byte[] vi) {
        return cipher("DESede", "DESede/CBC/PKCS5Padding", opmode, data, vi, secretKey);
    }

    private static byte[] cipher(String algorithm, String transformation, int opmode, byte[] data, byte[] iv, byte[] secretKey) {
        try {
            Key key = SecretKeyFactory.getInstance(algorithm).generateSecret(new DESedeKeySpec(secretKey));
            IvParameterSpec spec = new IvParameterSpec(iv);
            Cipher cipher = Cipher.getInstance(transformation);
            cipher.init(opmode, key, spec);
            return cipher.doFinal(data);
        } catch (InvalidKeyException | InvalidKeySpecException | NoSuchAlgorithmException | NoSuchPaddingException
                 | IllegalBlockSizeException | BadPaddingException | InvalidAlgorithmParameterException e) {
            throw new RuntimeException(e);
        }
    }

}
